//---------------------------------------------------------------------------


#pragma hdrstop

#include "TBooster.h"
#include "CoFunction.h"

//---------------------------------------------------------------------------

#pragma package(smart_init)
/*
__declspec(dllexport) float __fastcall BoosterWork(const float CutSpeed, const unsigned short WorkIndex);
__declspec(dllexport) TBooster __fastcall WhichBooster(const AnsiString ModelName);
__declspec(dllexport) AnsiString __fastcall WhichBoosterName(const unsigned short Index);
*/

extern TBoosterList BoosterList;

__fastcall TBooster::TBooster()
{
   FIsControlled = false;
   FCtrState = false;
   FCtrNumber = -1;
}

bool __fastcall TBooster::Initialize(const TMeasurementRate MeasurementRate)
{
	BeginPosition = ioBeginPosition * MeasurementRate.Length;
	EndPosition = ioEndPosition * MeasurementRate.Length;
   Positions.resize(Quantity);
	AveragePosition();
	WorkIndex = Index;
   return true;
}



float __fastcall TBooster::Woks(const unsigned short CutTrackNumber,
										  const int CutNumber,
										  const float CutSpeed,
										  const float Begin, const float End,
										  const float NowTime, const TAxesType AxesType)
{
	unsigned short Q;
	float W;

	if (FCtrNumber == -1 || FIsControlled)
	{
		Q = PassQuantity(CutTrackNumber, CutNumber, Begin, End, NowTime, CutSpeed, AxesType);
		if (Q < 1) return 0;
		W = Work(CutSpeed) * Q;
	}
	else
		W = 0;
	return W;
}

float __fastcall TBooster::Work(const float CutSpeed)
{
	float W;

	switch (WorkIndex)
	{
		case 4000:
			W = 0;
			break;
		case 4001:
			if (CutSpeed < 0.6944)
				W = -0.075;
			else if (CutSpeed < 0.9722)
				W = -0.08;
			else if (CutSpeed < 1.25)
				W = -0.075;
			else if (CutSpeed < 1.38)
				W = -0.065;
			else if (CutSpeed < 1.65)
				W = -0.055;
			else
				W = -0.05;
			break;
		case 4002:
			if (CutSpeed < 0.6944)
				W = -0.085;
			else if (CutSpeed < 0.9722)
				W = -0.09;
			else if (CutSpeed < 1.25)
				W = -0.085;
			else if (CutSpeed < 2)
				W = -0.07;
			else if (CutSpeed < 2.5)
				W = -0.065;
			else
				W = -0.055;
			break;
		default:
			W = -2000;
	}
	return W;
}

void __fastcall TBooster::ChangeCtrState(const bool Value)
{
   FIsControlled = Value;
};

void __fastcall TBooster::SetControlled(const bool Value)
{
   if (FCtrNumber != -1) FIsControlled = Value;
};


TBooster & __fastcall TBooster::operator = (const TBooster & t)
{
   FCtrNumber = t.FCtrNumber;
   FCtrState = t.FCtrState;
   FIsControlled = t.FIsControlled;
   Model = t.Model;
	WorkNumber = t.WorkNumber;
	Index = t.Index;
	
   return *this;
}

TBooster & __fastcall TBooster::operator = (const AnsiString ModelName)
{
//	*this = WhichBooster(ModelName);

   return *this;
}

__fastcall TBoosters::TBoosters()
{
}

bool __fastcall TBoosters::Initialize(const TMeasurementRate MeasurementRate)
{
   unsigned short i, q;
   q = size();
   for (i = 0; i < q; i++)
   {
		if(!at(i).Initialize(MeasurementRate)) return false;
   }
   return true;
}

TBoosters & __fastcall TBoosters::operator = (const TBoosters & t)
{
   unsigned short i, q;

   clear();
   q = t.size();
   for (i = 0; i < q; i++)
   {
      push_back(t[i]);
   }
   return *this;
}

void __fastcall TBoosters::Add(const AnsiString ModelName,
                               const float Begin, const float End,
                               const unsigned short Quantity,
                               const unsigned short MinTrack, const unsigned short MaxTrack,
                               const int CtrNumber)
{
   TBooster Booster;

   Booster = ModelName;
	Booster.BeginPosition = Begin;
   Booster.EndPosition = End;
   Booster.Quantity = Quantity;
   Booster.CtrNumber = CtrNumber;
   Booster.SetMinMaxTrack(MinTrack, MaxTrack);

   push_back(Booster);
}

float __fastcall TBoosters::Works(const unsigned short CutTrackNumber, const int CutNumber,
											 const float CutSpeed,
											 const float Begin, const float End,
											 const float NowTime, const TAxesType AxesType)
{
   unsigned short i, q;
   float W = 0;
   q = size();
   for (i = 0; i < q; i++)
   {
		W += at(i).Woks(CutTrackNumber, CutNumber, CutSpeed, Begin, End, NowTime, AxesType);
   }
   return W;
}

__fastcall TBoosterList::TBoosterList()
{
	New("NotExist", 0, 0);
   New("+101", 4001, -0.4);
	New("+102", 4002, -0.4);
}

bool __fastcall TBoosterList::Initialize(void)
{

}

void __fastcall TBoosterList::New(const AnsiString ModelName, const unsigned short Index,
											 const float BaseWork)
{
	TBooster Booster;

	Booster.Model = ModelName;
	Booster.WorkNumber = Index;
	Booster.BaseWork = BaseWork;
	Booster.Index = Index;

	push_back(Booster);
}

unsigned short __fastcall TBoosterList::Index(const AnsiString ModelName)
{
	unsigned short i, q;
	q = size();

	for (i = 0; i < q; i++)
		if (ModelName == at(i).Model) return at(i).Index;

	return 0;
}

AnsiString __fastcall TBoosterList::Model(const unsigned short Index)
{
	int i, q;

	q = size();
	for (i = 0; i <= q; i++)
	{
		if (at(i).Index == Index)
			return at(i).Model;
	}
	return at(0).Model;
}


TBooster __fastcall TBoosterList::Which(const unsigned short ModelIndex)
{
	int i, q;
	q = size();
	for (i = 0; i < q; i++) {
		if (at(i).ModelIndex == ModelIndex) {
			return at(i);
		}
	}
	return at(0);
}

TBooster __fastcall TBoosterList::Which(const AnsiString ModelName)
{
	int i, q;
	q = size();
	for (i = 0; i < q; i++) {
		if (at(i).Model == ModelName) {
			return at(i);
		}
	}
	return at(0);
}


void __fastcall TBooster::ChangeCtrState(void)
{
   FIsControlled = !FIsControlled;
}


void __fastcall TBooster::Load(const int Handle)
{
	ioBeginPosition = ReadFloat(Handle);
	ioEndPosition = ReadFloat(Handle);
	Index = ReadFloat(Handle);
	Model = BoosterList.Model(Index);
   Quantity = ReadFloat(Handle);
   CtrNumber = ReadFloat(Handle);
};

void __fastcall TBooster::Save(const int Handle)
{
	WriteFloat(Handle, ioBeginPosition);
	WriteFloat(Handle, ioEndPosition);
   WriteFloat(Handle, Index);
   WriteFloat(Handle, Quantity);
   WriteFloat(Handle, CtrNumber);
};

void __fastcall TBoosters::Load(const int Handle)
{
   unsigned short i ,q;
   clear();
   q = ReadFloat(Handle);
   resize(q);
   for (i = 0; i < q; i++)
      at(i).Load(Handle);
};

void __fastcall TBoosters::Save(const int Handle)
{
   unsigned short i, q;
   q = size();
   WriteFloat(Handle, q);
   for (i = 0; i < q; i++)
      at(i).Save(Handle);
};

